package com.fone.player.storage;

import java.util.concurrent.atomic.AtomicInteger;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.database.sqlite.SQLiteOpenHelper;

import com.fone.player.storage.download.SaveCacheDataUtil;
import com.fone.player.util.FoneUtil;
import com.fone.player.util.L;

public class FoneDatabase implements IFoneDatabase {
	private static final String TAG = "FoneDatabase";

	private static FoneOpenHelper sFoneOpenHelper;

	private static final String DATABASE_NAME = "fonePlayer.db";
	public static byte[] _writeLock = new byte[0];

	private static SQLiteDatabase mSQLiteDatabase = null;
	private static final FoneDatabase mFoneDatabase = new FoneDatabase();
	private AtomicInteger mOpenCounter = new AtomicInteger();

	private FoneDatabase() {

	}

	public static synchronized void init(Context context) {
		if (sFoneOpenHelper == null) {
			sFoneOpenHelper = new FoneOpenHelper(context, DATABASE_NAME, null,
					StorageConfig.DATABASE_CURRENT_VERSION);
		}

	}

	public static FoneDatabase getInstance() {
		return mFoneDatabase;
	}

	/**
	 * get SQLiteDatabase instance
	 * 
	 * @return SQLiteDatabase
	 */
	public SQLiteDatabase openDatabase() {
		if (mSQLiteDatabase == null) {
			mSQLiteDatabase = sFoneOpenHelper.getWritableDatabase();

		}

		if (mSQLiteDatabase != null) {
			while (mSQLiteDatabase.isDbLockedByCurrentThread()
					|| mSQLiteDatabase.isDbLockedByOtherThreads()) {
				// db is locked, keep looping
				L.w(TAG, "openDatabase", "mSQLiteDatabase locked.");

			}
			L.v(TAG, "openDatabase", "mSQLiteDatabase unlocked.");
		} else {
			L.v(TAG, "openDatabase", "mSQLiteDatabase=null");
		}

		return mSQLiteDatabase;
	}

	/**
	 * get SQLiteDatabase instance
	 * 
	 * @param isReadable
	 *            是否只读
	 * @return SQLiteDatabase
	 */
	public synchronized SQLiteDatabase openDatabase(boolean isReadable) {
		// L.v(TAG, "openDatabase", "start ");

		if (mOpenCounter.incrementAndGet() == 1) {

			// 第一次获取
			if (mSQLiteDatabase == null) {
				if (sFoneOpenHelper != null) {
					if (isReadable) {
						mSQLiteDatabase = sFoneOpenHelper.getReadableDatabase();
					} else {
						mSQLiteDatabase = sFoneOpenHelper.getWritableDatabase();

					}
				} else {
					L.e(TAG, "openDatabase",
							"is not init, call init(..) method first.");
				}
			} else {

				long time = 1000;
				long currentTime = System.currentTimeMillis();
				int i = 0;// 次数
				while ((System.currentTimeMillis() <= currentTime + time)
						&& i < 20) {
					// L.w(TAG, "openDatabase", "isDbLockedByOtherThreads="
					// + mSQLiteDatabase.isDbLockedByOtherThreads());
					// 锁定就等待
					if (!mSQLiteDatabase.isDbLockedByOtherThreads()
							&& !mSQLiteDatabase.isOpen()) {
						if (sFoneOpenHelper != null) {
							if (isReadable) {
								mSQLiteDatabase = sFoneOpenHelper
										.getReadableDatabase();
							} else {
								mSQLiteDatabase = sFoneOpenHelper
										.getWritableDatabase();

							}

						} else {
							L.e(TAG, "openDatabase",
									"is not init, call init(..) method first.");
						}

						break;
					}
					i++;
				}

			}

		}

		// L.v(TAG, "openDatabase", "end ");

		return mSQLiteDatabase;

	}

	/**
	 * 关闭数据库
	 */
	public synchronized void close() {

		// if (mSQLiteDatabase != null) {
		//
		// if (mOpenCounter.decrementAndGet() == 0) {
		// // Closing database
		// mSQLiteDatabase.close();
		//
		// }
		// }
	}

	static class FoneOpenHelper extends SQLiteOpenHelper {

		public FoneOpenHelper(Context context, String name,
				CursorFactory factory, int version) {
			super(context, name, factory, version);
		}

		@Override
		public void onCreate(SQLiteDatabase db) {
			L.i(TAG, "onCreate", "start");

			// 创建数据库
			StorageConfig.createDatabase(db);

			// 插入两条快速播放记录
			FoneUtil.iniFastPlayData(db);

			// fix,重新安装客户端，原来客户端中缓存的视频没有了
			SaveCacheDataUtil.getInstance().initOfflineCacheDatabase(db);
		}

		@Override
		public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
			L.i(TAG, "onUpgrade", "oldVersion=" + oldVersion + " newVersion="
					+ newVersion);
			if (newVersion > oldVersion) { // 旧版本升到新版本

				// 选用合适的数据库升级方案,进行升级
				StorageConfig.upgradeDatabase(db, oldVersion);

			}
		}
	}
}
